﻿/*
 * ShpSelectCommand
 * 
 * initial implementation : 20.12.2008
 *
 * Copyright (c) Adam Sida, asida@centrum.cz.
 * All rights reserved.
 * 
 * for license see Petra.Gis.License.txt
 */
using System;
using System.Text.RegularExpressions;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.Data.Common;
using Petra.Gis.DataServices;
using Petra.Gis.Geometry;
using Petra.Gis.Geometry.Support;
//using Petra.Gis.ReferenceSystemServices;
using Petra.Gis.DataServices.Metadata;


namespace Petra.Gis.DataServices.SHP
{
  public partial class ShpSelectCommand : SpatialDbCommand
  {



    // Implement the default constructor here.
    public ShpSelectCommand()
      :base()
    {
      //_parameters = new ShpDbParameterCollection();
    }



    // Implement other constructors here.
    public ShpSelectCommand(string cmdText)
      : base(cmdText)
    {
      //this.CommandText = cmdText;
    }




    public ShpSelectCommand(string cmdText, ShpConnection connection)
      : base(cmdText, connection)
    {
      //this.Connection = connection;
      //this.CommandText = cmdText;

      //internal wrapped sql command must get normal SqlConnection
      //it is accessible via extensions ;-)
      //prepareSpatialMetadata();
    }




    public ShpSelectCommand(string cmdText, ShpConnection connection, DbTransaction txn)
      : this(cmdText, connection)
    {

      throw new NotSupportedException();
      //_trans = txn;

      //prepareSpatialMetadata();
    }






    public override bool DesignTimeVisible
    {
      get { return false; }
      set {  }
    }




    protected string _cmdText;


    public override string CommandText
    {
      get { return _cmdText; }
      set 
      {
        // if text not null or empty
        if (value != null && value != "")
        {
          _cmdText = value;
          //Metadata = getFeatureMetadata();
        }
         
      }
    }





    public override int CommandTimeout
    {
      /*
       * The sample does not support a command time-out. As a result,
       * for the get, zero is returned because zero indicates an indefinite
       * time-out period. For the set, throw an exception.
       */
      get { return 0; }
      set {  }
    }





    public override CommandType CommandType
    {
      get { return CommandType.TableDirect; }
      set 
      {
        if (value != CommandType.TableDirect)
          throw new ArgumentException("only " + CommandType.TableDirect.ToString() + " supported");
      }
    }





    protected override DbConnection DbConnection
    {
      get { return this.Connection; }
      set { this.Connection = (ShpConnection)value; }
    }





    protected ShpConnection _connection;

    new public ShpConnection Connection
    {
      get { return _connection; }
      set
      {

        /*
         * The connection is associated with the transaction
         * so set the transaction object to return a null reference if the connection 
         * is reset.
         */
        if (_connection != value)
          this.Transaction = null;

        _connection = value;
      }
    }




    //protected SptlDbParameterCollection _parameters;

    //new public SptlDbParameterCollection Parameters
    //{
    //  get { return _parameters; }
    //}





    //protected override DbParameterCollection DbParameterCollection
    //{
    //  get { return this.Parameters; }
    //}





    /// <summary>
    /// file based, reads shp from local drive
    /// </summary>
    public override FeatureDataSourceTypeEnum FeatureDataSourceType
    {
      get
      {
        return FeatureDataSourceTypeEnum.FileBasedDataSource;
      }
    }




    new public DbTransaction Transaction
    {
      /*
       * Set the transaction. Consider additional steps to ensure that the transaction
       * is compatible with the connection, because the two are usually linked.
       */
      get { return null; }
      set { }
    }




    protected override DbTransaction DbTransaction
    {
      /*
       * Set the transaction. Consider additional steps to ensure that the transaction
       * is compatible with the connection, because the two are usually linked.
       */
      get { return this.Transaction; }
      set { this.Transaction = value; }
    }



    public override UpdateRowSource UpdatedRowSource
    {
      get { return UpdateRowSource.None; }
      set {  }
    }



    /****
     * IMPLEMENT THE REQUIRED METHODS.
     ****/
    public override void Cancel()
    {
      //_sqlCmd.Cancel();
    }





    new public SptlDbParameter CreateParameter()
    {
      return new SptlDbParameter();
    }


    protected override DbParameter CreateDbParameter()
    {
      return this.CreateParameter();
    }





    public override int ExecuteNonQuery()
    {
      /*
       * ExecuteNonQuery is intended for commands that do
       * not return results, instead returning only the number
       * of records affected.
       */

      throw new NotSupportedException();

    }



    new public ShpDbReader ExecuteReader()
    {
      // validate before run, SpatialDbCommand.validateBeforeRun()
      validateBeforeRun();

      //try prepare spatial metadata
      //prepareSpatialMetadata();

      //prepare spatial filter
      if (this.Parameters.Count > 0)
        prepareSpatialFilters();

      //object p = _sqlCmd.Parameters[1];

      return getShpDataReader();
    }




    new public ShpDbReader ExecuteReader(CommandBehavior behavior)
    {
      // validate before run
      validateBeforeRun();

      //try prepare spatial metadata
      //prepareSpatialMetadata();

      //prepare spatial filter
      if (this.Parameters != null)
        prepareSpatialFilters();

      return getShpDataReader();
    }




    protected override DbDataReader ExecuteDbDataReader(CommandBehavior behavior)
    {
      return this.ExecuteReader(behavior);
    }




    private ShpDbReader getShpDataReader()
    {
      System.Text.Encoding tmpEnc = null;
      BoundingBox tmpBounds = null;

      if (_connection.Extensions.ContainsKey("TextEncoding"))
        tmpEnc = (System.Text.Encoding)_connection.Extensions["TextEncoding"];

      if (this.Parameters.ContainsKey("Petra.Gis.DataServices.FeatureSpatialFilter"))
      {
        FeatureSpatialFilter SptlfilterSet = (FeatureSpatialFilter)this.Parameters["Petra.Gis.DataServices.FeatureSpatialFilter"].Value;
        tmpBounds = SptlfilterSet.Bounds;
      }

      return new ShpDbReader(this.Connection.DataSource + "\\" + _cmdText + ".shp",
                             tmpEnc, 
                             tmpBounds);
    }





    public override object ExecuteScalar()
    {

      throw new NotSupportedException();

    }




    public override void Prepare()
    {
      // The sample Prepare is a no-op.
    }

    /*public void Dispose()
    {
      this.Dispose(true);
      System.GC.SuppressFinalize(this);
    }
    */




    protected override void Dispose(bool disposing)
    {
      /*
       * Dispose of the object and perform any cleanup.
       */
      //base.Dispose();
    }

  }
}

